<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <title>vue-select</title>
    <link rel="stylesheet" href="./css/init.css">
    <!-- 字体 -->
    <link rel="stylesheet" href="./css/font-awesome.min.css">
    <style>
    .content {
        width: 80%;
        height: 80%;
        margin: 50px auto;
    }
    /* vue select 样式 */
    
    .vue-select-style {
        width: 150px;
        height: 30px;
        font-size: 14px;
        position: relative;
        -webkit-user-select: none;
        /* Chrome all / Safari all /opera15+*/
        -moz-user-select: none;
        /* Firefox all */
        -ms-user-select: none;
        /* IE 10+ */
        user-select: none;
    }
    
    .vue-select-style>div:first-child {
        height: inherit;
    }
    
    .vue-select-style>div>input {
        width: 100%;
        height: inherit;
        display: block;
        cursor: pointer;
        outline: 0;
        padding-left: 8px;
        border: 1px solid #e6e6e6;
        color: #48576a;
        background-color: #fff;
        border-radius: 6px;
        -webkit-user-select: none;
        /* Chrome all / Safari all /opera15+*/
        -moz-user-select: none;
        /* Firefox all */
        -ms-user-select: none;
        /* IE 10+ */
        user-select: none;
        transition: border-color .3s cubic-bezier(.65, .05, .35, .5);
    }
    
    .vue-select-style>div>input:hover {
        border-color: #57c5f7;
    }
    
    .vue-select-style>div>i {
        position: absolute;
        top: 7px;
        right: 5px;
        transition: all 0.3s;
    }
    
    .vue-select-style dl {
        width: inherit;
        position: absolute;
        left: 0;
        top: 35px;
        padding: 2px 0;
        z-index: 999;
        min-width: 100%;
        border: 1px solid #d2d2d2;
        max-height: 300px;
        overflow-y: auto;
        background-color: #fff;
        border-radius: 3px;
        box-shadow: 0 2px 4px rgba(0, 0, 0, .12);
        box-sizing: border-box;
    }
    
    .vue-select-style dl dt,
    .vue-select-style dl dd {
        padding: 0 8px;
        line-height: 32px;
        white-space: nowrap;
        overflow: hidden;
        color: #48576a;
        text-overflow: ellipsis;
    }
    
    .vue-select-style dl dt {
        font-size: 12px;
        color: #48576a;
    }
    
    .vue-select-style dl dd {
        cursor: pointer;
    }
    
    .vue-select-style dl dd:hover {
        background-color: #f2f2f2;
    }
    
    .vue-select-style-active {
        transform: rotate(180deg);
    }
    /* 当前选项 */
    
    .is-this-opt {
        background-color: #b6e7ff !important;
    }
    
    .mrginT {
        margin: 50px;
    }
    </style>
</head>

<body>
    <div>
        <div class="content">
            <div>
                不可过滤：
                <vue-select :selectdata="pageSelectData" :is-filter="isFilter" id="select1">
                </vue-select>
                多选：
                <vue-select :selectdata="pageSelectData" :is-filter="isFilter" id="select2">
                </vue-select>
            </div>
            可过滤：
            <vue-select :selectdata="pageSelectData" :is-filter="isFilter" id="select3">
            </vue-select>
        </div>
    </div>
    <div id="app">
    </div>
</body>
<!-- select 组件 -->
<template id="vue-select">
    <div class="vue-select-style" :style="{height:height}">
        <div @click="inputClick()">
            <input type="text" v-model="selectdata.text" :readonly="isFilter">
            <i class="fa fa-angle-down" :class="{'vue-select-style-active':selectdata.show}"></i>
        </div>
        <dl v-show="selectdata.show" style="display: none;">
            <dd v-for="option in optionsFilter" :class="{'is-this-opt':option.val==selectdata.lastOpt}" @click="optClick(option)">
                <input type="checkbox" v-show="selectdata.isMulti" v-model="option.checked">
                <span v-text="option.text"></span>
            </dd>
        </dl>
    </div>
</template>
<!-- multiselect 组件 -->
<script src="js/vue.js"></script>
<script>
var app = new Vue({
    el: '#app',
    data: {
        li: [{
            check: true
        }, {
            check: true
        }, {
            check: true
        }]
    }
});
// 注册select组件
Vue.component('vue-select', {
    template: '#vue-select',
    props: {
        isFilter: Boolean,
        height: String,
        selectdata: {
            isMulti: Boolean, //是否是多选
            lastOpt: Number, //上一次选项
            val: Number,
            text: String,
            show: Boolean,
            options: Array
        }
    },
    data: function() {
        return this.selectdata;
    },
    watch: {
        selectdata: {
            handler: function(val, oldVal) {
                if (val.show) {

                };
            },
            deep: true
        }
    },
    created: function() {
        //新建时，让默认值等于第一个选项
        // this.selectdata.val = this.selectdata.options[0].val;
        // this.selectdata.text = this.selectdata.options[0].text;
        window.addEventListener('click', (e) => {
            //添加事件
            if (!this.$el.contains(e.target)) {
                if (this.selectdata.show == true) this.selectdata.show = false;
            }
        })
    },
    computed: {
        optionsFilter: function() {
            //过滤
            console.log(1)
            let temp = this.options.filter((item) => {
                return item.text.toLowerCase().indexOf(this.text.toLowerCase()) != -1
            });
            //是否为空
            return temp.length == 0 ? [{
                text: '无符合数据',
                val: -1
            }] : temp;
        }
    },
    methods: {
        inputClick: function() {
            //input事件
            this.selectdata.val = '';
            this.selectdata.text = '';
            this.selectdata.show = !this.selectdata.show;
            this.showOpt();
        },
        optClick: function(option, index) {
            //选项事件
            if (!this.selectdata.isMulti) {
                //不是多选
                this.selectdata.val = option.val;
                this.selectdata.text = option.text;
                this.selectdata.lastOpt = option.val;
                this.selectdata.show = !this.selectdata.show;
            } else {
                option.checked = !option.checked;
                console.log(option.checked);
            }
            // 当值未改变时不触发
            if (this.selectdata.val == option.val) return;
            // 触发该子组件事件
            this.$emit('select-change')
        },
        showOpt: function() {
            //根据距离下方的距离，判断展示方向
            //let a=this.$el.querySelector("dl").clientHeight;
            let elBottom = this.$el.getBoundingClientRect().bottom;
            let clintBottom = document.body.clientHeight;
            let bottom = clintBottom - elBottom;
            let dtHeight = (this.selectdata.options.length * 32) + 6;
            if (bottom < dtHeight) {
                this.$el.querySelector("dl").style.top = (0 - (dtHeight + 2)) + 'px';
            } else {
                this.$el.querySelector("dl").style.top = 34 + 'px';
            }
        }
    },
})
var pageSelectData = {
    lastOpt: null,
    val: 0,
    text: '',
    show: false,
    options: [{
        text: '100条/页',
        val: 100
    }, {
        text: '200条/页',
        val: 200
    }, {
        text: '400条/页',
        val: 400
    }]
};
var pageSelectData2 = {
    lastOpt: null,
    isMulti: true,
    val: 0,
    text: '',
    show: false,
    options: [{
        text: '小明',
        val: 100,
        checked: false
    }, {
        text: '小王',
        val: 200,
        checked: false
    }, {
        text: '王爸爸',
        val: 400,
        checked: false
    }]
};
var pageSelectData3 = {
    lastOpt: null,
    val: 0,
    text: '',
    show: false,
    options: [{
        text: '小明',
        val: 100
    }, {
        text: '小王',
        val: 200
    }, {
        text: '王爸爸',
        val: 400
    }]
};
var select1 = new Vue({
    el: '#select1',
    data: {
        height: '500px',
        isFilter: true,
        pageSelectData: pageSelectData
    }
});
var select2 = new Vue({
    el: '#select2',
    data: {
        height: '500px',
        isFilter: true,
        pageSelectData: pageSelectData2
    }
});
var select3 = new Vue({
    el: '#select3',
    data: {
        height: '500px',
        isFilter: false,
        pageSelectData: pageSelectData3
    }
});
</script>

</html>
